package com.innovation.wjrpc.rpc;

import com.innovation.wjrpc.codec.Decoder;
import com.innovation.wjrpc.codec.Encoder;
import com.innovation.wjrpc.communication.HTTPTransportClient;
import com.innovation.wjrpc.loader.TransportSelector;
import com.innovation.wjrpc.protocol.Request;
import com.innovation.wjrpc.protocol.Response;
import com.innovation.wjrpc.transport.TransportClient;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.IOUtils;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;

/**
 * @author innoyiya
 * @date 2021/9/8 12:16
 */
@Slf4j
public class HTTPRemoteInvoker extends RemoteInvoker {

    public HTTPRemoteInvoker(Class clazz, Encoder encoder, Decoder decoder, TransportSelector selector) {
        super(clazz, encoder, decoder, selector);
    }

    @Override
    public Response invokeRemote(Request request) {
        Response response;
        HTTPTransportClient client = null;
        try {

            client = (HTTPTransportClient)selector.select();

            byte[] outBytes = encoder.encode(request);
            InputStream receive = client.write(new ByteArrayInputStream(outBytes));
            byte[] inBytes = IOUtils.readFully(receive, receive.available());
            response = decoder.decode(inBytes, Response.class);
        } catch (IOException e) {
            log.warn(e.getMessage(), e);
            response = new Response();
            response.setCode(1);
            response.setMessage("RpcClient got error: " + e.getClass() + " : " + e.getMessage());
        } finally {
            if (client != null) {
                selector.release(client);
            }
        }

        return response;
    }
}
